package com.jiangjiang.eshop.schedule.stock;

import com.jiangjiang.eshop.order.dto.OrderInfoDTO;
import com.jiangjiang.eshop.order.dto.OrderItemDTO;
import com.jiangjiang.eshop.order.service.OrderService;
import com.jiangjiang.eshop.schedule.domain.GoodsAllocationStockEntity;
import com.jiangjiang.eshop.schedule.domain.GoodsStockEntity;
import com.jiangjiang.eshop.schedule.dto.SaleDeliveryScheduleResult;
import com.jiangjiang.eshop.schedule.dto.ScheduleOrderPickingItemDTO;
import com.jiangjiang.eshop.schedule.service.SaleDeliveryScheduler;
import com.jiangjiang.eshop.schedule.service.ScheduleGoodsAllocationStockDetailService;
import com.jiangjiang.eshop.schedule.service.ScheduleGoodsAllocationStockService;
import com.jiangjiang.eshop.schedule.service.ScheduleGoodsStockService;
import com.jiangjiang.eshop.wms.dto.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Component;

import java.util.*;
import java.util.function.Function;
import java.util.stream.Collectors;

/**
 * @ClassName ReturnGoodsInputScheduleStockUpdater
 * @Description TODO
 * @Author jhw
 * @Date 2021/8/30 23:18
 * @Version 1.0
 **/
@Component
@Scope("prototype")
public class ReturnGoodsInputScheduleStockUpdater extends AbstractScheduleStockUpdater {


    private ReturnGoodsInputOrderDTO returnGoodsInputOrderDTO;

    /**
     * 商品库存管理的DAO组件
     */
    @Autowired
    private ScheduleGoodsStockService goodsStockService;
    /**
     * 货位库存管理的DAO组件
     */
    @Autowired
    private ScheduleGoodsAllocationStockService goodsAllocationStockService;
    /**
     * 货位库存明细管理的DAO组件
     */
    @Autowired
    private ScheduleGoodsAllocationStockDetailService stockDetailService;

    /**
     * 销售出库调度器
     */
    @Autowired
    private SaleDeliveryScheduler saleDeliveryScheduler;
    /**
     * 订单中心接口
     */
    @Autowired
    private OrderService orderService;


    @Override
    protected void updateGoodsStock() throws Exception {

        List<ReturnGoodsInputOrderItemDTO> items = returnGoodsInputOrderDTO.getItems();
        Map<Long, Long> skuArrivalCountMap = items.stream().collect(Collectors.groupingBy(ReturnGoodsInputOrderItemDTO::getGoodSkuId,
                Collectors.summingLong(ReturnGoodsInputOrderItemDTO::getArrivalCount)));
        Set<Long> skuIds = items.stream().map(ReturnGoodsInputOrderItemDTO::getGoodSkuId).collect(Collectors.toSet());
        List<GoodsStockEntity> stockEntities = goodsStockService.queryBySkuIds(skuIds).stream().peek(entity -> {
            entity.setAvailableStockQuantity(
                    entity.getAvailableStockQuantity() +
                            skuArrivalCountMap.getOrDefault(entity.getGoodsSkuId(), 0L)
            );
            entity.setOutputStockQuantity(
                    entity.getOutputStockQuantity() -
                            skuArrivalCountMap.getOrDefault(entity.getGoodsSkuId(), 0L)
            );
        }).collect(Collectors.toList());

        goodsStockService.updateBatchById(stockEntities);

    }

    @Override
    protected void updateGoodsAllocationStock() throws Exception {
        OrderInfoDTO order = orderService.getOrderById(returnGoodsInputOrderDTO.getOrderId());
        Map<Long, OrderItemDTO> orderItemMap = order.getOrderItems()
                .stream()
                .collect(Collectors.toMap(OrderItemDTO::getGoodsSkuId, Function.identity()));
        for (ReturnGoodsInputOrderItemDTO item : returnGoodsInputOrderDTO.getItems()) {
            OrderItemDTO orderItemDTO = orderItemMap.get(item.getGoodSkuId());
            if(Objects.isNull(orderItemDTO)){
                throw new RuntimeException(String.format("订单:[%s]未查询到商品[%s]的购买记录",
                        returnGoodsInputOrderDTO.getOrderId(), item.getGoodSkuId()));
            }

            SaleDeliveryScheduleResult result =  saleDeliveryScheduler.getScheduleResult(orderItemDTO);
            List<ScheduleOrderPickingItemDTO> pickingItems = result.getPickingItems();
            for (ScheduleOrderPickingItemDTO pickingItem : pickingItems) {
                GoodsAllocationStockEntity entity = goodsAllocationStockService.
                        queryBySkuId(pickingItem.getGoodsAllocationId(), pickingItem.getGoodsSkuId());
                entity.setAvailableStockQuantity(entity.getAvailableStockQuantity() + pickingItem.getPickingCount());
                entity.setOutputStockQuantity(entity.getOutputStockQuantity() - pickingItem.getPickingCount());

                goodsAllocationStockService.updateById(entity);
            }


        }

    }

    @Override
    protected void updateGoodsAllocationStockDetail() throws Exception {
        for (ReturnGoodsInputOrderItemDTO item : returnGoodsInputOrderDTO.getItems()) {
            List<GoodsAllocationStockDetailDTO> stockDetails = item.getStockDetails();
            stockDetailService.saveBatchDetailDTO(stockDetails);
        }

    }

    @Override
    public void setParameter(Object parameter) {
        this.returnGoodsInputOrderDTO = (ReturnGoodsInputOrderDTO) parameter;
    }
}
